package com.wlz.single;

import java.io.IOException;
import java.net.InetSocketAddress;
import java.nio.ByteBuffer;
import java.nio.channels.ServerSocketChannel;
import java.nio.channels.SocketChannel;
import java.util.ArrayList;
import java.util.List;

/**
 * @author： wlz
 * @Date 2020/8/14 9:54
 * @description： TODO NIO 简单服务端
 * @version: 1.0
 *
 *  这种非阻塞实现可以让服务端节省下许多资源。但是这样的实现还是有弊端：
 * 我们在这里采用了轮询的方式来接收消息，每次都会轮询所有的连接，查看哪个套接字中有准备好的消息。
 * 在连接到服务端的连接还少的时候，这种方式是没有问题的，但是如果现在有100w个连接，此时再使用轮询的话，效率就变得十分低下。
 * 而且很大一部分的连接基本都不发消息的，在100w个连接中可能只有10w个连接会有消息，但是每次连接程序后我们都得去轮询，这是很不适合的。

 */
public class SingleNioServer {

    public static void main(String[] args) {

        List<SocketChannel> channelList = new ArrayList<SocketChannel>();
        ByteBuffer byteBuffer = ByteBuffer.allocate(1024);

        try {
            ServerSocketChannel serverSocketChannel = ServerSocketChannel.open();
            serverSocketChannel.bind(new InetSocketAddress(8080));
            serverSocketChannel.configureBlocking(false); // 设置为非阻塞

            while (true){
                SocketChannel socketChannel = serverSocketChannel.accept();

                if (socketChannel == null) {
                    Thread.sleep(1000);
                    System.out.println("没有客户端连接上来");
                    for (SocketChannel socketChannel1 : channelList) {
                        int k = socketChannel1.read(byteBuffer);
                        System.out.println("===== no connection =====");
                        if (k != 0) { // 有连接发来数据
                            byteBuffer.flip();
                            System.out.println(new String(byteBuffer.array()));
                        }
                    }
                }else {
                    socketChannel.configureBlocking(false);
                    channelList.add(socketChannel);
                    // 得到套接字，循环所有的套接字，通过套接字获取数据
                    for (SocketChannel socket : channelList) {
                        int k = socket.read(byteBuffer);
                        System.out.println("===== connection =====");
                        if(k != 0) {
                            byteBuffer.flip();
                            System.out.println(new String(byteBuffer.array()));
                        }
                    }
                }
            }


        } catch (IOException | InterruptedException e) {
            e.printStackTrace();
        }

    }
}
